#ifndef THREAD_POLL
#define THREAD_POLL 1
#include <thread>
#include <condition_variable>
#include <mutex>
#include <queue>
#include <memory>
#include <functional>
class ThreadPoll
{
public:
    ThreadPoll() = default;
    ThreadPoll(ThreadPoll && temp) = default;
    ~ThreadPoll()
    {
        if(poll_!=nullptr)
        {
            std::unique_lock<std::mutex> mtx(poll_->mtx_);
            poll_->isStop = true;
        }
        poll_->cond_.notify_all();
    }
    explicit ThreadPoll(int numthreads=12):poll_(std::make_shared<Poll>())
    {
        assert(numthreads>0);
        for(int i = 0 ; i<numthreads;i++)
        {
            std::thread
            (
                [this]()
                {
                    std::unique_lock<std::mutex> mtx(poll_->mtx_);
                    while(true)
                    {   
                        if(poll_->Task_.empty() == false)   //queue 非空,取走一个任务
                        {
                            auto task = std::move(poll_->Task_.front());
                            poll_->Task_.pop();
                            mtx.unlock();
                            task();         //执行任务
                            mtx.lock();     //准备下一轮的任务接取
                        }
                        else if(poll_->isStop == true)
                        {
                            break;
                        }
                        else
                        {   
                            poll_->cond_.wait(mtx); //等待任务
                        }
                    }
                }
            ).detach();
        }
    }
    template<class T>
    void addTask(T&& task)
    {
        std::unique_lock<std::mutex> mtx(poll_->mtx_);
        poll_->Task_.emplace(std::forward<T>(task));
        poll_->cond_.notify_one();  //唤醒一个正在等待的线程
    }
private:
    struct Poll
    {
        bool isStop;
        std::mutex mtx_;
        std::condition_variable cond_;
        std::queue<std::function<void()>> Task_;
    };
    
    std::shared_ptr<Poll> poll_;
};
#endif